<?php


namespace helper;


class Http
{

  /**
   * 以get模拟网络请求
   * @param string $url HTTP请求URL地址
   * @param array $query GET请求参数
   * @param array $options CURL参数
   * @return boolean|string
   */
  static public function get($url, $query = [], $options = [])
  {
    $options['query'] = $query;
    return self::request('get', $url, $options);
  }

  /**
   * 以post模拟网络请求
   * @param string $url HTTP请求URL地址
   * @param array $data POST请求数据
   * @param array $options CURL参数
   * @return boolean|string
   */
  static public function post($url, $data = [], $options = [])
  {
    $options['data'] = $data;
    return self::request('post', $url, $options);
  }

  /**
   * CURL模拟网络请求
   * @param string $method 请求方法
   * @param string $url 请求方法
   * @param array $options 请求参数[headers,data]
   * @return boolean|string
   */
  static public function request($method, $url, $options = [])
  {
    $curl = curl_init();
    // GET参数设置
    if (!empty($options['query'])) {
      $url .= (stripos($url, '?') !== false ? '&' : '?') . http_build_query($options['query']);
    }
    // CURL头信息设置
    if (!empty($options['headers'])) {
      curl_setopt($curl, CURLOPT_HTTPHEADER, $options['headers']);
    }
    // POST数据设置
    if (strtolower($method) === 'post') {
      curl_setopt($curl, CURLOPT_POST, true);
      curl_setopt($curl, CURLOPT_POSTFIELDS, self::_buildHttpData($options['data']));
    }
    curl_setopt($curl, CURLOPT_URL, $url);
    curl_setopt($curl, CURLOPT_TIMEOUT, 60);
    curl_setopt($curl, CURLOPT_HEADER, false);
    curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
    curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false);
    curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, false);
    list($content) = [curl_exec($curl), curl_close($curl)];
    return $content;
  }

  /**
   * POST数据过滤处理
   * @param array $data 需要处理的数据
   * @param boolean $build 是否编译数据
   * @return array|string
   */
  static private function _buildHttpData($data, $build = true)
  {
    if (!is_array($data)) return $data;
    foreach ($data as $key => $value) if (is_object($value) && $value instanceof \CURLFile) {
      $build = false;
    } elseif (is_string($value) && class_exists('CURLFile', false) && stripos($value, '@') === 0) {
      if (($fileName = realpath(trim($value, '@'))) && file_exists($fileName)) {
        list($build, $data[$key]) = [false, new \CURLFile($fileName)];
      }
    }
    return $build ? http_build_query($data) : $data;
  }

  /**
   * 使用证书，以post方式提交xml到对应的接口url
   * @param string $url 请求的地址
   * @param array $data POST提交的内容
   * @param string $ssl_cer 证书Cer路径 | 证书内容
   * @param string $ssl_key 证书Key路径 | 证书内容
   * @param int $second 设置请求超时时间
   * @return bool|mixed
   */
  static public function httpsPost($url, $data, $ssl_cer = null, $ssl_key = null, $second = 30)
  {
    $curl = curl_init();
    curl_setopt($curl, CURLOPT_URL, $url);
    curl_setopt($curl, CURLOPT_TIMEOUT, $second);
    curl_setopt($curl, CURLOPT_HEADER, false);
    curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false);
    curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, false);
    curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
    if (!is_null($ssl_cer) && file_exists($ssl_cer) && is_file($ssl_cer)) {
      curl_setopt($curl, CURLOPT_SSLCERTTYPE, 'PEM');
      curl_setopt($curl, CURLOPT_SSLCERT, $ssl_cer);
    }
    if (!is_null($ssl_key) && file_exists($ssl_key) && is_file($ssl_key)) {
      curl_setopt($curl, CURLOPT_SSLKEYTYPE, 'PEM');
      curl_setopt($curl, CURLOPT_SSLKEY, $ssl_key);
    }
    curl_setopt($curl, CURLOPT_POST, true);
    curl_setopt($curl, CURLOPT_POSTFIELDS, self::_buildHttpData($data));
    list($content, $status) = array(curl_exec($curl), curl_getinfo($curl), curl_close($curl));
    return (intval($status["http_code"]) === 200) ? $content : false;
  }
}
